package com.csii.activiti.server.core.entity;


import com.csii.activiti.server.core.constant.FlowNodeTypeConstant;
import com.fasterxml.jackson.annotation.JsonFormat;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

@Data
@ApiModel("流程配置")
public class ActFlowConfiguration {
    @ApiModelProperty("主键")
    private String id;
    @ApiModelProperty("单实列")
    private List<ActFlowNode> nodes;
    @ApiModelProperty("多实列")
    private List<ActFlowMultiNode> multiNodes;
    @ApiModelProperty("全局配置项")
    private ActFlowConfigurationItem flowConfigurationItem;
    @ApiModelProperty("发起人表单配置项")
    private List<ActFlowFormContentSetting> initiatorFormContentSetting;
    @ApiModelProperty("流程名称")
    private String flowName;
    @ApiModelProperty("流程key")
    private String flowKey;
    @ApiModelProperty("流程描述")
    private String description;
    @ApiModelProperty("图标类型")
    private String iconType;
    @ApiModelProperty("流程状态")
    private String status;
    @ApiModelProperty("表单定义数据")
    private String formJson;
    @ApiModelProperty("分组ID")
    private String groupId;
    @ApiModelProperty("排序")
    private Integer sort;
    @ApiModelProperty("是否已经发布")
    private Boolean publish;
    @ApiModelProperty("最后更新时间")
    @JsonFormat(timezone = "GMT+8",pattern = "yyyy-MM-dd HH:mm:ss")
    private Date lastUpdateTime;
    @ApiModelProperty("最后更新人")
    private String lastUpdateUsername;
    @ApiModelProperty("模式=url(patternUrl)表单(patternForm)")
    private String pattern;
    @ApiModelProperty("回显条件json")
    private String echoConditionJson;
    @ApiModelProperty("回显环节条件json")
    private String echoLinkConditionJson;
    @ApiModelProperty("流程字段json")
    private String flowColumnJson;
    @ApiModelProperty("回调签名key")
    private String flowSignKey;
    @ApiModelProperty("前端通用数据")
    private String webCommonData;
    @ApiModelProperty("列表权限展示")
    private List<String> permissionList;
    @ApiModelProperty("摘要展示")
    private String summary;
    @ApiModelProperty("重新提交规则")
    private String resubmitRule;

    public List<ActFlowNode> allFlowNode(){
        if (nodes != null){
            return allFlowNode(nodes);
        }
        if (multiNodes == null){
            return null;
        }
        List<ActFlowNode> allNodeList = new ArrayList<>();
        for (ActFlowMultiNode multiNode : multiNodes) {
            allNodeList.addAll(allFlowNode(multiNode.getNodes()));
        }
        return allNodeList;
    }

    private List<ActFlowNode> allFlowNode(List<ActFlowNode> nodes){
        List<ActFlowNode> resultNodes = new ArrayList<>();
        if (nodes != null && !nodes.isEmpty()){
            resultNodes.addAll(nodes);
            List<ActFlowNode> linkNodes = nodes.stream().filter(item -> FlowNodeTypeConstant.LINK_NODE.equals(item.getNodeType())).collect(Collectors.toList());
            for (ActFlowNode linkNode : linkNodes) {
                for (ActFlowMultiNode actFlowMultiNode : linkNode.getNodeLink()) {
                    resultNodes.addAll(allFlowNode(actFlowMultiNode.getNodes()));
                }
            }
        }
        return resultNodes;
    }


    public List<ActFlowCondition> allFlowNodeCondition(){
        if (nodes != null){
            return allFlowNodeCondition(nodes);
        }
        if (multiNodes == null){
            return null;
        }
        List<ActFlowCondition> allFlowCondition = new ArrayList<>();
        for (ActFlowMultiNode multiNode : multiNodes) {
            allFlowCondition.addAll(multiNode.employCondition());
            allFlowCondition.addAll(allFlowNodeCondition(multiNode.getNodes()));
        }
        return allFlowCondition;
    }

    private List<ActFlowCondition> allFlowNodeCondition(List<ActFlowNode> nodes){
        List<ActFlowCondition> resultConditions = new ArrayList<>();
        if (nodes != null && !nodes.isEmpty()){
            List<ActFlowNode> linkNodes = nodes.stream().filter(item -> FlowNodeTypeConstant.LINK_NODE.equals(item.getNodeType())).collect(Collectors.toList());
            for (ActFlowNode linkNode : linkNodes) {
                for (ActFlowMultiNode actFlowMultiNode : linkNode.getNodeLink()) {
                    resultConditions.addAll(actFlowMultiNode.employCondition());
                    resultConditions.addAll(allFlowNodeCondition(actFlowMultiNode.getNodes()));
                }
            }
        }
        return resultConditions;
    }

}
